package com.wwz.interceptor;

import com.wwz.annoation.Path;
import com.wwz.path.PathHandler;
import com.wwz.path.PathMappingCreator;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.lang.Nullable;
import org.springframework.stereotype.Component;
import org.springframework.web.HttpRequestHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.context.request.ServletWebRequest;
import org.springframework.web.context.request.async.WebAsyncManager;
import org.springframework.web.context.request.async.WebAsyncUtils;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.*;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;
import org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter;
import org.springframework.web.servlet.resource.ResourceHttpRequestHandler;
import org.springframework.web.servlet.view.json.MappingJackson2JsonView;
import org.springframework.web.util.NestedServletException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.lang.invoke.MethodHandle;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.Enumeration;
import java.util.Iterator;

/**
 * @author wwz
 */
@Component
public class ExHandlerInterceptor extends HttpRequestHandlerAdapter implements ApplicationContextAware {

    private static ApplicationContext applicationContext;


   /* @Nullable
    @Override
    public ModelAndView handle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        Method originMethod = PathMappingCreator.getPathMethod().get(request.getRequestURI());
        if(originMethod!=null){
            HandlerMethod handlerMethod = new HandlerMethod(getBean(originMethod.getDeclaringClass()),originMethod);
            handler.handleInternal(request, response,handlerMethod);
        }

        return null;
    }*/
  /*  @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
       *//* if(handler instanceof HandlerMethod){
            HandlerMethod handlerMethod = (HandlerMethod)handler;
            Method method = handlerMethod.getMethod();
            Path path = method.getAnnotation(Path.class);
            if(path!=null){
                Method originMethod = PathMappingCreator.getPathMethod().get(request.getRequestURI());
                if(originMethod!=null){
                    originMethod.invoke(getBean(originMethod.getDeclaringClass()),getParams(originMethod,request));
                }
            }
        }else if(handler instanceof ResourceHttpRequestHandler){
            Method originMethod = PathMappingCreator.getPathMethod().get(request.getRequestURI());
            if(originMethod!=null){
                originMethod.invoke(getBean(originMethod.getDeclaringClass()),getParams(originMethod,request));
            }

        }*//*
        return true;
    }*/

   /* @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
        Method originMethod = PathMappingCreator.getPathMethod().get(request.getRequestURI());
        if(originMethod!=null){
            if(originMethod.isAnnotationPresent(ResponseBody.class)){
                 modelAndView = new ModelAndView(new MappingJackson2JsonView()).addObject("result",originMethod.invoke(getBean(originMethod.getDeclaringClass()),getParams(originMethod,request))+"");

            }else{
                modelAndView = new ModelAndView( originMethod.invoke(getBean(originMethod.getDeclaringClass()),getParams(originMethod,request))+"");
            }

        }
    }
*/

    private Object[] getParams(Method originMethod ,HttpServletRequest request){
       Parameter[] parameters = originMethod.getParameters();
       Object[] params = new Object[parameters.length];
      for(int i = 0;i<parameters.length;i++){
          params[i] = request.getParameter(parameters[i].getName());
      }
     return params;
    }


    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        ExHandlerInterceptor.applicationContext = applicationContext;
    }

    public static <T> T  getBean(Class<T> clazz) {
        return applicationContext != null?applicationContext.getBean(clazz):null;
    }

}
